/// ****************************************************************************
/// Author:	        Robin Zhu
/// Create Date:	2011-11-1
/// Purpose: 		SQL语句编码类文件
/// ****************************************************************************
/// Modify By		Date			Remark
/// Robin           2012-3-23       给GetMethodCall接口增加参数
/// Robin           2012-6-14       增加SkipRecords接口，以便生成跳过前n条记录的语句
/// Robin           2013-7-23       增加GetSubQuery虚方法，方便生成不同数据库的子查询
/// ****************************************************************************

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Linq.Expressions;
using System.Reflection;

namespace RB.DataAccess
{
    /// <summary>
    /// SQL语句编码类，根据特定的SQL语言变种生成表名、字段名、操作符、常量等
    /// </summary>
    public abstract class SqlEncoder
    {
        public abstract string GetBooleanExpression(string propertyName);

        public abstract string GetOperator(Type operandType, ExpressionType expressionType, bool isNullValue, out bool isMethodCall);

        public abstract string GetBooleanExpression(bool value);

        public abstract string GetFieldName(string propertyName, string tableAlias);

        public abstract string GetTableName(string typeName, string tableAlias);

        public abstract string GetConstant(object value);

        public virtual string GetFieldConstant<T>(PropertyInfo propertyInfo, object value)
        {
            return GetConstant(value);
        }

        public abstract string GetMethodCall(string method, string caller, string[] arguments, Type callerType);

        public abstract string GetTopN(int takeCount, string query);

        /// <summary>
        /// 生成跳过n条记录的语句
        /// </summary>
        /// <param name="skipCount"></param>
        /// <param name="beforeSkip"></param>
        /// <param name="orderClause"></param>
        /// <returns></returns>
        public abstract string SkipRecords(int skipCount, string beforeSkip, string orderClause);

        public virtual string GetSubQuery(string partialQuery, string alias)
        {
            string selectClause = "(SELECT TOP (100) PERCENT " + partialQuery + ")";
            if (alias != null)
            {
                selectClause += " AS " + alias;
            }
            else
            {
                selectClause += " AS tQuery" + DateTime.Now.Ticks.ToString();
            }
            return selectClause;
        }
    }
}
